﻿using ApiGateway.Config;
using ApiGateway.Interface;
using ApiGateway.IpBlack;
using RpcHelper.Config;

namespace ApiGateway.PlugIn
{
    /// <summary>
    /// IP黑名单
    /// </summary>
    internal class IpBlackListPlugIn : BasicPlugIn, IIpBlackListPlugIn
    {
        private IIpBlack _IpBack;

        private IpBlackConfig _Config;

        public override bool IsEnable => this._Config.IsEnable;

        public IpBlackListPlugIn() : base("IpBack")
        {
            this._Config = LocalConfig.Local.GetValue<IpBlackConfig>("gateway:ipBack", new IpBlackConfig());
            LocalConfig.Local.RefreshEvent += this._Refresh;
        }
        protected override void _InitPlugIn()
        {
            if (!this._Config.IsEnable)
            {
                return;
            }
            else if (!this._Config.IsLocal)
            {
                this._IpBack = new RemoteIpBack();
            }
            else
            {
                this._IpBack = new LocalIpBlack();
            }
            this._IpBack.Init(this._Config);
        }
        protected override void _Dispose()
        {
            if (!this._Config.IsEnable)
            {
                this._IpBack?.Dispose();
                this._IpBack = null;
            }
        }
        private void _Refresh(IConfigCollect config, string name)
        {
            if (name == "gateway:ipBack" || name.StartsWith("gateway:ipBack:"))
            {
                IpBlackConfig back = config.GetValue<IpBlackConfig>("gateway:ipBack");
                if (!back.IsEnable && this._Config.IsEnable)
                {
                    this._Config = back;
                    base._ChangeEvent();
                }
                else if (back.IsEnable && !this._Config.IsEnable)
                {
                    this._Config = back;
                    base._ChangeEvent();
                }
                else if (back.IsEnable && this._IpBack != null)
                {
                    this._Config = back;
                    this._IpBack.Init(this._Config);
                }

            }
        }

        public bool IsLimit(string ip)
        {
            if (!this._IpBack.IsInit)
            {
                return false;
            }
            return this._IpBack.IsLimit(ip);
        }
    }
}
